<script setup>
import { CopyDocument } from '@element-plus/icons-vue'
import {ref, onMounted, onBeforeUnmount, watch} from 'vue'
import { ElMessage } from 'element-plus'
import { useMessageStore } from '@/stores/message.js'
import httpInstance from '@/api/http'

const messageStore = useMessageStore()
let socket = null

const initWebSocket = () => {
  socket = new WebSocket(`${httpInstance.defaults.baseURL}/ws/chat`)

  socket.onopen = () => {
    console.log('WebSocket连接已建立')
  }

  socket.onmessage = (event) => {
    const receivedMessage = JSON.parse(event.data)
    addMessage(receivedMessage)
  }

  socket.onclose = () => {
    console.log('WebSocket连接已关闭')
  }

  socket.onerror = (error) => {
    console.error('WebSocket错误:', error)
  }
}

const sendMessage = (msg) => {
  if (socket.readyState === WebSocket.OPEN) {
    socket.send(msg)
  } else {
    console.error('WebSocket未连接')
  }
}

const addMessage = (msg) => {
  if (msg.type === 'text') {
    messageStore.messageList.push(msg)
  }
  if(messageStore.show) {
    messageStore.readMessageId.push(msg.id)
  }
}

const handleCopy = (text) => {
// 如果是安全上下文，优先使用现代 API
  if (window.isSecureContext) {
    navigator.clipboard.writeText(text).then(
        () => ElMessage.success('已复制到剪贴板'),
        (err) => {
          console.error('Clipboard API 失败:', err)
          // 备用方案
          fallbackCopy(text)
        }
    )
  } else {
    // 非安全上下文，使用降级方案
    fallbackCopy(text)
  }
}

// 降级复制方法
function fallbackCopy(text) {
  const textarea = document.createElement('textarea')
  textarea.value = text
  textarea.style.position = 'fixed'
  textarea.style.opacity = '0'
  textarea.style.zIndex = '-1000'
  document.body.appendChild(textarea)
  textarea.focus()
  textarea.select()
  try {
    const successful = document.execCommand('copy')
    if (successful) {
      ElMessage.success('已复制到剪贴板')
    } else {
      ElMessage.error('复制失败')
    }
  } catch (err) {
    ElMessage.error('复制失败')
  }
  document.body.removeChild(textarea)
}

const newMessage = ref('')
const sendNewMessage = () => {
  if (newMessage.value.trim()) {
    sendMessage(newMessage.value)
    newMessage.value = ''
  }
}

onMounted(() => {
  initWebSocket()
})

onBeforeUnmount(() => {
  if (socket) {
    socket.close()
  }
})

watch(() => messageStore.show, (val) => {
  if (val) {
    messageStore.markAllAsRead()
  }
})
</script>

<template>
  <el-dialog
      v-model="messageStore.show"
      title="消息"
      width="80%"
      :style="{ height: '75%' }"
  >
    <div class="message-list">
      <template v-if="messageStore.messageList.length > 0">
        <div
            v-for="(msg, index) in messageStore.messageList"
            :key="index"
            :class="['message-wrapper', msg.my ? 'right' : 'left']"
        >
          <el-card class="message-card" shadow="hover">
            <div class="message-header">
              <span class="sender" :class="{ mine: msg.my }">{{ msg.sender }}</span>
              <span class="time">{{ msg.time }}</span>
            </div>
            <div class="message-body">
              <div class="message-content">{{ msg.data }}</div>
              <el-button
                  @click="handleCopy(msg.data)"
                  :icon="CopyDocument"
                  size="small"
                  circle
                  text
                  class="copy-btn"
              />
            </div>
          </el-card>
        </div>
      </template>

      <el-empty v-else description="暂无消息" />
    </div>

    <!-- 输入框 -->
    <div class="message-input">
      <el-input
          v-model="newMessage"
          type="textarea"
          :rows="1"
          placeholder="请输入消息..."
          style="flex: 1;"
      />
      <el-button
          type="primary"
          style="margin-left: 10px;"
          @click="sendNewMessage"
      >
        发送
      </el-button>
    </div>
  </el-dialog>
</template>

<style scoped>
.message-list {
  padding: 10px;
  max-height: 400px;
  overflow-y: auto;
  display: flex;
  flex-direction: column;
  gap: 12px;
}

.message-wrapper {
  display: flex;
  width: 100%;
}

.message-wrapper.left {
  justify-content: flex-start;
}

.message-wrapper.right {
  justify-content: flex-end;
}

.message-card {
  width: 70%;
  border-radius: 12px;
  padding: 12px;
  background-color: #f8f9fa;
}

.message-header {
  display: flex;
  justify-content: space-between;
  font-size: 13px;
  color: #999;
  margin-bottom: 8px;
}

.sender {
  font-weight: bold;
  color: #409EFF;
}

.sender.mine {
  color: #67C23A;
}

.time {
  font-style: italic;
}

.message-body {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
}

.message-content {
  white-space: pre-wrap;
  word-break: break-word;
  line-height: 1.6;
  flex: 1;
  user-select: text;
  color: #333;
}

.copy-btn {
  flex-shrink: 0;
  color: #999;
}

.message-input {
  display: flex;
  margin-top: 20px;
}
</style>

